/**
 * www.easyplatform.cn ©2016
 */
package cn.easyplatform.studio.web.editors.version;

import cn.easyplatform.entities.EntityInfo;
import cn.easyplatform.lang.Strings;
import cn.easyplatform.studio.StudioApp;
import cn.easyplatform.studio.cmd.entity.GetEntryCmd;
import cn.easyplatform.studio.cmd.entity.GetObjectCmd;
import cn.easyplatform.studio.cmd.version.GetExportInfoContainCmd;
import cn.easyplatform.studio.cmd.version.GetListCmd;
import cn.easyplatform.studio.context.Contexts;
import cn.easyplatform.studio.utils.StudioUtil;
import cn.easyplatform.studio.utils.WebUtils;
import cn.easyplatform.studio.vos.RepoVo;
import cn.easyplatform.studio.web.editors.Editor;
import cn.easyplatform.studio.web.editors.EditorCallback;
import cn.easyplatform.studio.web.layout.WorkbenchController;
import cn.easyplatform.studio.web.views.impl.AbstractView;
import cn.easyplatform.type.EntityType;
import org.zkoss.util.resource.Labels;
import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.Page;
import org.zkoss.zk.ui.event.Event;
import org.zkoss.zk.ui.event.Events;
import org.zkoss.zk.ui.util.Clients;
import org.zkoss.zul.*;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

/**
 * @author <a href="mailto:shiny_vc@163.com">陈云亮</a> <br/>
 * @since 2.0.0 <br/>
 */
public class ExportEditor extends AllExportEditor {

    private final static String LAST_VERSION = "SELECT lastNo from ep_export_info WHERE lastNo in (SELECT MAX(lastNo) from ep_export_info  WHERE projectId = ?)";

    private Textbox content;

    private Combobox type;

    private Textbox user;

    private Datebox beginDate;

    private Datebox endDate;

    private Intbox beginVersion;

    private Intbox endVersion;

    private Checkbox lastVersion;

    public ExportEditor(WorkbenchController workbench, String id) {
        super(workbench, id);
    }

    @Override
    public void create(Object... args) {
        Idspace is = createPanel(Labels.getLabel("editor.export.title"), "~./images/svn/export.gif", "~./include/editor/version/export.zul");
        for (Component comp : is.getFellows()) {
            String id = comp.getId();
            if (id.equals("versionExport_textbox_id")) {
                this.id = (Textbox) comp;
            } else if (id.equals("versionExport_textbox_name")) {
                this.name = (Textbox) comp;
            } else if (id.equals("versionExport_textbox_desp")) {
                this.desp = (Textbox) comp;
            } else if (id.equals("versionExport_textbox_content")) {
                this.content = (Textbox) comp;
            } else if (id.equals("versionExport_textbox_type")) {
                this.type = (Combobox) comp;
            } else if (id.equals("versionExport_datebox_beginDate")) {
                this.beginDate = (Datebox) comp;
            } else if (id.equals("versionExport_datebox_endDate")) {
                this.endDate = (Datebox) comp;
            } else if (id.equals("versionExport_intbox_beginVersion")) {
                this.beginVersion = (Intbox) comp;
                Number obj = (Number) StudioApp.execute(beginVersion, new GetObjectCmd(LAST_VERSION, new Object[]{Contexts.getProject().getId()}));
                if (obj != null)
                    this.beginVersion.setValue(obj.intValue() + 1);
            } else if (id.equals("versionExport_intbox_endVersion")) {
                this.endVersion = (Intbox) comp;
            } else if (id.equals("versionExport_checkbox_lastVersion")) {
                this.lastVersion = (Checkbox) comp;
            } else if (id.equals("versionExport_textbox_user")) {
                this.user = (Textbox) comp;
            } else if (id.equals("versionExport_tree_sources")) {
                this.sources = (Tree) comp;
            } else if (id.equals("versionExport_textbox_comment")) {
                this.comment = (Textbox) comp;
            } else if (id.equals("versionExport_tree_targets")) {
                this.targets = (Listbox) comp;
            } else if (comp instanceof Button || comp instanceof Image) {
                comp.addEventListener(Events.ON_CLICK, this);
            } else if (comp instanceof Checkbox) {
                comp.addEventListener(Events.ON_CHECK, this);
            }
        }
    }

    private void redraw(Component btn) {
        this.sources.getTreechildren().getChildren().clear();
        String tp = type.getSelectedIndex() == -1 ? "" : type.getSelectedItem().getValue().toString();
        RepoVo vo = new RepoVo();
        vo.setId(id.getValue());
        vo.setName(name.getValue());
        vo.setDesp(desp.getValue());
        vo.setContent(content.getValue());
        vo.setType(tp);
        vo.setBeginDate(beginDate.getValue());
        vo.setEndDate(endDate.getValue());
        vo.setBeginVersion(beginVersion.getValue());
        vo.setEndVersion(endVersion.getValue());
        vo.setUser(user.getValue());
        vo.setLastVersion(lastVersion.isChecked());
        List<EntityInfo> data = StudioApp.execute(btn, new GetListCmd(vo));
        int size = data.size();
        Treechildren tc = sources.getTreechildren();
        String prevId = null;
        for (int i = 0; i < size; i++) {
            EntityInfo e = data.get(i);
            if (!lastVersion.isChecked()) {
                if ((i + 1 < size && e.getId().equals(data.get(i + 1).getId()))) {
                    if (!e.getId().equals(prevId)) {
                        Treeitem p = new Treeitem();
                        p.setLabel(e.getId());
                        p.setParent(sources.getTreechildren());
                        tc = new Treechildren();
                        tc.setParent(p);
                    }
                } else if (!e.getId().equals(prevId))
                    tc = sources.getTreechildren();
                prevId = e.getId();
            } else
                tc = sources.getTreechildren();
            Treeitem li = new Treeitem();
            Treerow row = new Treerow();
            row.appendChild(new Treecell(e.getId()));
            row.appendChild(new Treecell(e.getName()));
            row.appendChild(new Treecell(e.getDescription()));
            row.appendChild(new Treecell(e.getType()));
            row.appendChild(new Treecell(e.getUpdateDate().toString()));
            row.appendChild(new Treecell(e.getUpdateUser()));
            row.appendChild(new Treecell(e.getVersion() + ""));
            li.addEventListener(Events.ON_DOUBLE_CLICK, this);
            li.setValue(e);
            row.setParent(li);
            tc.appendChild(li);
        }
    }

    @Override
    public void dispatch(Event event) {
        if (event.getName().equals(Events.ON_CLICK)) {
            Component comp = event.getTarget();
            if (comp.getId().equals("versionExport_button_query")) {
                redraw(comp);
            } else if (comp.getId().equals("versionExport_image_chooseAllBtn")) {
                select(false);
            } else if (comp.getId().equals("versionExport_image_chooseBtn")) {
                select(true);
            } else if (comp.getId().equals("versionExport_image_removeBtn")) {
                unselect(true);
            } else if (comp.getId().equals("versionExport_image_removeAllBtn")) {
                unselect(false);
            } else if (comp.getId().equals("versionExport_toolbarbutton_export")) {
                export(comp);
            }
        } else if (event.getName().equals(Events.ON_CHECK)) {
            Checkbox r = (Checkbox) event.getTarget();
            doCheck(r);
        } else if (event.getName().equals(Events.ON_DOUBLE_CLICK)) {
            Treeitem ti = (Treeitem) event.getTarget();
            EntityInfo e = ti.getValue();
            compare(e);
        }
    }

    private void doCheck(Checkbox cbx) {
        if (cbx.getValue().equals("1") || cbx.getValue().equals("3")) {
            Iterator<Component> itr = sources.queryAll("treeitem").iterator();
            while (itr.hasNext()) {
                Treeitem ti = (Treeitem) itr.next();
                if (ti.getValue() != null) {
                    if (cbx.getValue().equals("1"))
                        ti.setSelected(cbx.isChecked());
                    else
                        ti.setSelected(!ti.isSelected());
                }
            }
        } else if (lastVersion.isChecked()) {
            int pos = sources.getPagingChild().getActivePage() * sources.getPagingChild().getPageSize();
            List<Treeitem> data = new ArrayList<Treeitem>(sources.getItems());
            for (; pos < data.size(); pos++) {
                Treeitem ti = data.get(pos);
                ti.setSelected(cbx.isChecked());
            }
        }
    }

    private void compare(final EntityInfo e) {
        EntityInfo orig = StudioApp.execute(sources, new GetEntryCmd(e.getId()));
        if (orig != null) {
            AbstractView.createVersionView(new EditorCallback<String>() {
                @Override
                public String getValue() {
                    if (e.getType().equals(EntityType.REPORT.getName()))
                        return StudioUtil.convertReportContent(e.getContent());
                    return e.getContent();
                }

                @Override
                public void setValue(String value) {
                }

                @Override
                public String getTitle() {
                    return Labels.getLabel("entity.content.compare", new String[]{e.getId()});
                }

                @Override
                public Page getPage() {
                    return sources.getPage();
                }

                @Override
                public Editor getEditor() {
                    return ExportEditor.this;
                }
            }, orig.getType().equals(EntityType.REPORT.getName()) ? StudioUtil.convertReportContent(orig.getContent()) : orig.getContent()).doOverlapped();
        }
    }

    private void unselect(boolean selectedFlag) {
        if (selectedFlag) {
            if (targets.getSelectedCount() > 0) {
                List<Listitem> items = new ArrayList<Listitem>();
                for (Listitem li : targets.getSelectedItems())
                    items.add(li);
                for (Listitem li : items)
                    li.detach();
            }
        } else
            targets.getItems().clear();
    }

    private void select(boolean selectFlag) {
        for (Treeitem sel : sources.getItems()) {
            if (selectFlag && !sel.isSelected())
                continue;
            if (sel.getValue() != null) {
                boolean exists = false;
                EntityInfo s = sel.getValue();
                for (Listitem li : targets.getItems()) {
                    EntityInfo t = li.getValue();
                    if (s.getId().equals(t.getId())) {
                        exists = true;
                        break;
                    }
                }
                if (!exists) {
                    Listitem li = new Listitem();
                    li.appendChild(new Listcell(s.getId()));
                    li.appendChild(new Listcell(s.getName()));
                    li.appendChild(new Listcell(s.getDescription()));
                    li.appendChild(new Listcell(s.getType()));
                    li.appendChild(new Listcell(s.getUpdateDate().toString()));
                    li.appendChild(new Listcell(s.getUpdateUser()));
                    li.appendChild(new Listcell(s.getVersion() + ""));
                    li.setValue(s);
                    targets.appendChild(li);
                }
            }
        }
    }

    //导出
    protected void export(Component btn) {
        if (targets.getItems().isEmpty()) {
            WebUtils.showError(Labels.getLabel("editor.export.empty"));
            return;
        }
        if (Strings.isBlank(comment.getValue())) {
            WebUtils.notEmpty(Labels.getLabel("editor.export.comment"));
            return;
        }
        Clients.clearWrongValue(btn);
        //打包保存
        List<EntityInfo> entites = new ArrayList<EntityInfo>();
        int max = 0;
        int min = 1000000000;
        for (Listitem li : targets.getItems()) {
            EntityInfo e = li.getValue();
            if (e.getVersion() > max)
                max = e.getVersion();
            if (e.getVersion() < min)
                min = e.getVersion();
            entites.add(e);
        }
        Boolean isContain = StudioApp.execute(new GetExportInfoContainCmd(Contexts.getProject().getId() + "_" + min + "-" + max));
        if (isContain) {
            WebUtils.showInfo(Labels.getLabel("editor.export.error.doubleID"));
        } else {
            StudioUtil.export(btn, entites, comment.getValue(), min, max);
        }
    }
}
